#ifndef __TV_STREAM_SOURCE_PINS_H__
#define __TV_STREAM_SOURCE_PINS_H__

struct SEEKDATA
{
	REFERENCE_TIME rtSeekTo;
	BOOL bSycn;
};
//
enum
{
	MIN_VIDEO_SAMPLE_BUFFER = 131072, //128KB
	MIN_AUDIO_SAMPLE_BUFFER = 65536,  // 64KB
};
//

class CTVStreamSourcePin : public CSourceStream,
						  public CSourceSeeking
{
public:

    CTVStreamSourcePin(TCHAR *pObjectName, HRESULT *phr, CSource *pFilter, bool isAudio);
    ~CTVStreamSourcePin();
	
    // Override the version that offers exactly one media type
	const AM_MEDIA_TYPE * GetType();
    HRESULT GetMediaType(CMediaType *pMediaType);
    HRESULT DecideBufferSize(IMemAllocator *pAlloc, ALLOCATOR_PROPERTIES *Request);
	//
	STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, void ** ppv);
	STDMETHODIMP QueryInterface(REFIID riid, void **ppv);
	STDMETHODIMP_(ULONG) AddRef();                                    
	STDMETHODIMP_(ULONG) Release();
	//IMediaSeeking
	virtual HRESULT ChangeStart() = 0;
	virtual HRESULT ChangeStop()  = 0;
	virtual HRESULT ChangeRate()  = 0;
	//
	void SetMediaTime();
	//
    HRESULT FillBuffer(IMediaSample *pSample);
	HRESULT DoBufferProcessingLoop(void);
    // Quality control
	STDMETHODIMP Notify(IBaseFilter *pSelf, Quality q);
//	HRESULT Active(void);
    HRESULT BeginFlushData(void);
    HRESULT EndFlushData(void);
    void    KillPin();

public:
	//
	void SetSeekData(REFERENCE_TIME rtSeekTo);
	//
	BOOL IsSeeking();
	void SetAnotherPin(CTVStreamSourcePin* pPin);
	//
	//
	//

private:
    BOOL DumpoutData();
	void SetDefaultMediaType();
	void GetFirstMediaType();
	void SetInfor(TVMEDIATYPESECTION tv);
	BOOL CheckMediaType(PBYTE pData);
	CMediaType m_MediaType;
	//
	BYTE* m_Data;
	//
	
	volatile BOOL m_bPinAvaible;
	volatile BOOL m_bSync;
    volatile LONG m_bFlushforSync;

protected:
	virtual HRESULT OnThreadStartPlay(void);
	virtual HRESULT OnThreadDestroy(void);
	virtual void	RawSync(LONGLONG start) = 0;

	SampleHeader        m_header;
	bool                m_isAudioPin;
	bool				m_bTryGetMediaType;
	//
	int                 m_iVideoSampleSize;
	int                 m_iAudioSampleSize;
	//
	CCritSec            m_critsec_rtCurrTime_SeekData;
	SEEKDATA            m_SeekData;
	//
	CTVStreamSource*    m_pFilter;
	CTVStreamSourcePin* m_pAnotherPin;

#ifdef USE_LOG
	FILE* log;
#endif
	//
protected:
	CCritSec m_crisecllBaseTime;
	LONGLONG m_llBaseTime;
	//
};
#endif// __TV_STREAM_SOURCE_PINS_H__